using System;
using System.IO;
using Canlipe.Lib;
using Canlipe.Utils;
using System.Linq;
using Canlipe.ServiceInterfaces;
using System.Collections.Generic;

namespace Canlipe.Lib
{
	public class MainProcessor
	{
		private ILogger _logger;
        private IContentParser _contentParser;

		public MainProcessor (ILogger logger, IContentParser contentParser)
		{
            this._logger = logger;
            this._contentParser = contentParser;
			this.Categories = new List<Category> ();
			this.Posts = new List<Post> ();
		}

		private bool CheckPrerequisites ()
		{
			if (SourceFolder == null) {
				this._logger.Log ("Source folder cannot be null");
				return false;
			}
			if (OutputFolder == null) {
                this._logger.Log("Output folder cannot be null");
				return false;
			}
			if (!Directory.Exists (SourceFolder)) {
                this._logger.Log("Source folder does not exist");
				return false;
			}

			return true;
		}

		public bool Run ()
		{
			if (!CheckPrerequisites ()) {
				return false;
			}

			// @TODO: replace with some provider stuff
			var postsFolder = Path.Combine (this.SourceFolder, "Posts");
			foreach (var dir in Directory.EnumerateDirectories(postsFolder)) {
				var currentCategory = new Category { Title = Path.GetDirectoryName(dir) };
				foreach (var post in Directory.EnumerateFiles(dir)) {
					var newPost = Post.FromPath (post, this._logger, this._contentParser);
					currentCategory.Posts.Add (newPost);
					this.Posts.Add (newPost);
				}

				if (currentCategory.Posts.Count > 0) {
					this.Categories.Add (currentCategory);
				}
			}
			this.Posts = this.Posts.OrderByDescending (o => o.Date).ToList ();

			// clean the output folder
			FileHelper.DeleteAllFilesInFolder (this.OutputFolder);

			// copy static crap
			FileHelper.CopyFilesRecursively (
				"DefaultTheme/static",
				this.OutputFolder);

			// configure razor
			RazorEngine.Razor.AddResolver (this.ResolveTemplate);

			// build index.html
			//string indexTemplate = File.ReadAllText ("DefaultTheme/templates/index.html");
			var indexPage = RazorEngine.Razor.Parse (
				this.ResolveTemplate ("index.html"),
				new RazorModel<MainProcessor> (this, this), "index");
			File.WriteAllText (
				Path.Combine (this.OutputFolder, "index.html"),
				indexPage);

			// build all posts
			foreach (var post in this.Posts) {
				var postPage = RazorEngine.Razor.Parse (
					this.ResolveTemplate ("post.html"),
					new RazorModel<Post> (this, post),
					"post");

				var actualFilePath = Path.Combine (this.OutputFolder, post.Url);
				var actualFolderPath = Path.GetDirectoryName (actualFilePath);
				if (!Directory.Exists (actualFilePath)) {
					Directory.CreateDirectory (actualFolderPath);
				}
				File.WriteAllText (
					actualFilePath,
					postPage);
			}

			return true;
		}

		private string ResolveTemplate (string template)
		{
			var filePath = "DefaultTheme/templates/" + template;
			if (!File.Exists (filePath))
				return null;
			return File.ReadAllText (filePath);
		}

		public List<Post> Posts { get; set; }

		public List<Category> Categories { get; set; }

		public string SourceFolder { get; set; }

		public string OutputFolder { get; set; }

		public string BaseUrl { get; set; }
	}
}

